<?php
namespace App\Http\Controllers\Api;

use App\Lib\WeApp\WeApp;
use App\Models\Mp\WxMpFreePublish;
use App\Models\Mp\WxMpMessage;
use App\Models\Mp\WxMpMessageReply;
use App\Models\Shop\WxShopOrder;
use App\Models\User\WxUser;
use App\Models\WxOrder;
use App\Wen\Utils\GatewayUtils;
use App\Wen\Utils\OrderUtils;
use App\Wen\Utils\Settings;
use App\Wen\Utils\ShopUtils;
use App\Wen\Utils\StrUtils;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;

class WeChatController extends BaseController
{
    public function mini_event_handler(Request $request){
        $weapp = new WeApp('mini');
        if($weapp){
            $messageEvent = $weapp->getMessageEvent();
            if($messageEvent){
                $messageEvent
                    ->with(function($message, \Closure $next) use (&$messageEvent, &$request, &$weapp){
                        // 处理事件
                        if($message->MsgType === 'event'){
                            if($message->Event == 'debug_demo'){
                                return 'minisns debug_demo 测试成功';
                            }else if($message->Event == 'trade_manage_order_settlement'){
                                $transaction_id = $message->transaction_id;
                                $the_order = WxOrder::where('order_serial_number', $transaction_id)->first();
                                if($the_order){
                                    if($the_order->order_state == 5 && !_empty_($the_order->order_serial_number) && $the_order->order_serial_platform === 0 && $the_order->order_serial_platform_type == 'mini'){
                                        // 在等待确认收货
                                        $infomange = $weapp->getDeliverInfoManage();
                                        $wechat_order = $infomange->getDeliverOrder($transaction_id);
                                        if($wechat_order){
                                            if(in_array(_array_key($wechat_order, 'order_state', 0), [3,4])){
                                                DB::beginTransaction();
                                                try {
                                                    WxOrder::where('id', $the_order->id)->update([
                                                        'order_state' => 1
                                                    ]);
                                                    OrderUtils::order_obtains($the_order, 0);
                                                    DB::commit();
                                                    return '';
                                                } catch (\Exception $e) {
                                                    DB::rollBack();
                                                    _logger_(__file__, __line__, $e->getMessage());
                                                }
                                            }
                                        }
                                    }
                                }else{
                                    $shop_order = WxShopOrder::where('serial_number', $transaction_id)->first();
                                    if($shop_order){
                                        if($shop_order->status == 8){
                                            if($shop_order->pay_status == 2 && !_empty_($shop_order->serial_number) && $shop_order->serial_platform === 0 && $shop_order->serial_platform_type == 'mini'){
                                                $infomange = $weapp->getDeliverInfoManage();
                                                $wechat_order = $infomange->getDeliverOrder($transaction_id);
                                                if($wechat_order){
                                                    if(in_array(_array_key($wechat_order, 'order_state', 0), [3,4])){
                                                        if(ShopUtils::coupon_to_finish($shop_order, 0, '')){
//                                                        GatewayUtils::success(GatewayUtils::uid2client_id($scanner), 17);
                                                            GatewayUtils::success(GatewayUtils::uid2client_id($shop_order->user_id), 17);
                                                            return '';
                                                        }
                                                    }
                                                }
                                            }
                                        }else if($shop_order->status == 10){
                                            if($shop_order->pay_status == 2 && !_empty_($shop_order->serial_number) && $shop_order->serial_platform === 0 && $shop_order->serial_platform_type == 'mini'){
                                                $deliver_manage = $weapp->getDeliverInfoManage();
                                                $wechat_order = $deliver_manage->getDeliverOrder($shop_order->serial_number);
                                                if($wechat_order){
                                                    if(in_array(_array_key($wechat_order, 'order_state', 0), [3,4])){
                                                        DB::beginTransaction();
                                                        try {
                                                            // todo:
                                                            $ship_at = date('Y-m-d H:i:s', time());
                                                            WxShopOrder::withTrashed()->where('id', $shop_order->id)->update([
                                                                'has_virtual' => 1,
                                                                'ship_at' => $ship_at,
                                                                'status' => 2,
                                                            ]);
                                                            ShopUtils::paied_content_process($shop_order->id);
                                                            DB::commit();
                                                            return '';
                                                        } catch (\Exception $e) {
                                                            DB::rollBack();
                                                            _logger_(__file__, __line__, $e->getMessage());
                                                        }

                                                    }
                                                }
                                            }
                                        }
                                    }
                                }
                            }else{
                                return '';
                            }
                            return '';
                        }
                        return $next($message);
                    })
                    ->with(function($message, \Closure $next) use (&$messageEvent, &$request){
                        $mp_open_id = $message->FromUserName;
                        // 处理消息
                        if($message->MsgType == 'text'){
                            $chat_content = $message->Content;
                            return '';
                        }
                        return $next($message);
                    })
                    ->with(function($message, \Closure $next) use (&$messageEvent){
                        // 处理客服消息
                        return $next($message);
                    });
                return $messageEvent->response($request);
            }
        }
    }

    public function mp_event_handler(Request $request){
        $weapp = new WeApp('mp');
        if($weapp){
            $mpServicer = $weapp->getMpServicer();
            if($mpServicer){
                $mpServicer
                    ->with(function($message, \Closure $next) use (&$mpServicer, &$request){
                        // 处理事件
                        if($message->MsgType === 'event'){
                            if($message->Event == 'debug_demo'){
                                return 'minisns debug_demo 测试成功';
                            }else if( $message->Event == 'unsubscribe'){
                                // 取消关注
                                $mp_open_id = $message->FromUserName;
                                _logger_(__file__, __line__, $mp_open_id . '已取消关注公众号' . $message->ToUserName);
                                return '';
                            }else if( $message->Event == 'subscribe' || $message->Event == 'SCAN'){
                                $mp_open_id = $message->FromUserName;
                                $eventKey = $message->EventKey;
                                if(StrUtils::startsWith($eventKey, 'qrscene_user:bind:') || StrUtils::startsWith($eventKey, 'user:bind:')){
                                    if(StrUtils::startsWith($eventKey, 'user:bind:')){
                                        $user_id = (int)(str_replace('user:bind:', '', $eventKey));
                                    }else{
                                        $user_id = (int)(str_replace('qrscene_user:bind:', '', $eventKey));
                                    }
                                    if($user_id > 0){
                                        $alread_user = WxUser::withTrashed()->where('weixin_mp_openid', $mp_open_id)->first();
                                        if($alread_user && $alread_user->id > 0){
                                            if(_empty_($alread_user->weixin_unionid)){
                                                DB::beginTransaction();
                                                try {
                                                    // todo:
                                                    WxUser::withTrashed()->where('id', $alread_user->id)->update([
                                                        'weixin_mp_openid' => null
                                                    ]);
                                                    WxUser::withTrashed()->where('id', $user_id)->update([
                                                        'weixin_mp_openid' => $mp_open_id
                                                    ]);
                                                    DB::commit();
                                                } catch (\Exception $e) {
                                                    DB::rollBack();
                                                    _logger_(__file__, __line__, $e->getMessage());
                                                }
                                            }
                                        }else{
                                            WxUser::withTrashed()->where('id', $user_id)->update([
                                                'weixin_mp_openid' => $mp_open_id
                                            ]);
                                        }
                                    }
                                }else if(StrUtils::startsWith($eventKey, 'user:scene:') || StrUtils::startsWith($eventKey, 'qrscene_user:scene:')){
                                    if(StrUtils::startsWith($eventKey, 'qrscene_user:scene:')){
                                        $scene_arr = explode(':', str_replace('qrscene_user:scene:', '', $eventKey));
                                    }else{
                                        $scene_arr = explode(':', str_replace('user:scene:', '', $eventKey));
                                    }
                                    $user_id = $scene_arr[0] ?? 0;
                                    $to_scene = $scene_arr[1] ?? 0;
                                    $to_scene_id = $scene_arr[2] ?? 0;
                                    $tenant_id = $scene_arr[3] ?? 0;
                                    if($user_id > 0){
                                        $alread_user = WxUser::withTrashed()->where('weixin_mp_openid', $mp_open_id)->first();
                                        if($alread_user && $alread_user->id > 0){
                                            if(_empty_($alread_user->weixin_unionid)){
                                                DB::beginTransaction();
                                                try {
                                                    // todo:
                                                    WxUser::withTrashed()->where('id', $alread_user->id)->update([
                                                        'weixin_mp_openid' => null
                                                    ]);
                                                    WxUser::withTrashed()->where('id', $user_id)->update([
                                                        'weixin_mp_openid' => $mp_open_id
                                                    ]);
                                                    DB::commit();
                                                } catch (\Exception $e) {
                                                    DB::rollBack();
                                                    _logger_(__file__, __line__, $e->getMessage());
                                                }
                                            }
                                        }else{
                                            WxUser::withTrashed()->where('id', $user_id)->update([
                                                'weixin_mp_openid' => $mp_open_id
                                            ]);
                                        }

                                        if($to_scene == 31){
                                            return [
                                                "MsgType" => "text",
                                                "Content" => '<a href="'.Settings::get('app_h5_home', '').'/#/pagesA/mine/members/members'.'">购买会员点这里</a>'
                                            ];
                                        }else if($to_scene == 84){
                                            return [
                                                "MsgType" => "text",
                                                "Content" => '<a href="'.Settings::get('app_h5_home', '').'/#/pagesC/promotion/post?id='.$to_scene_id.'">笔记推广点这里</a>'
                                            ];
                                        }else if($to_scene == 163){
                                            return [
                                                "MsgType" => "text",
                                                "Content" => '<a href="'.Settings::get('app_h5_home', '').'/#/pagesA/mine/unlock/unlock?user_id='.$to_scene_id.'">解除账号限制点这里</a>'
                                            ];
                                        }else if($to_scene == 80001){
                                            return [
                                                "MsgType" => "text",
                                                "Content" => '<a href="'.Settings::get('app_h5_home', '').'/#/pages/user/user?id='.$to_scene_id.'&contact_apply=1'.'">付费获取Ta的联系方式点这里</a>'
                                            ];
                                        }else{
                                            return [
                                                "MsgType" => "text",
                                                "Content" => '无效的参数'
                                            ];
                                        }
                                    }
                                }else{
                                    $res = $mpServicer->getUserInfo($mp_open_id);
                                    if($res['code'] == 200 && _array_key($res, 'unionid', '')){
                                        // 如果不存在这个用户
                                        $data = [
                                            'openId'=>$mp_open_id, 'avatarUrl'=>'', 'city'=>'', 'country'=>'',
                                            'province'=>'', 'language'=>'','nickName' => Settings::get('default_user_name', '微信用户'),
                                            'gender'=>0, 'unionId'=>$res['unionid']
                                        ];
                                        $wxUserModel = new WxUser();
                                        $user_id = $wxUserModel->registerUser($data, 'mp');
                                    }
                                }
                                $mp_message_id = WxMpMessageReply::where('word', 'event_subscribe')->value('mp_message_id');
                                if($mp_message_id && $mp_message_id > 0){
                                    $mp_message = WxMpMessage::find($mp_message_id);
                                    if($mp_message){
                                        return $mp_message->normal();
                                    }
                                }
                                return '';
                            }else if( $message->Event == 'TEMPLATESENDJOBFINISH'){
                                return '';
                            }else if( $message->Event == 'PUBLISHJOBFINISH'){
                                if($message->publish_id){
                                    $updates = [
                                        'publish_status' => $message->publish_status,
                                        'article_id' => $message->article_id,
                                        'article_url' => $message->article_url
                                    ];
                                    if(!_empty_($updates['article_id'])){
                                        $updates['media_id'] = null;
                                    }
                                    WxMpFreePublish::where('publish_id', $message->publish_id)->update($updates);
                                }
                            }else{
                                return '';
                            }
                            return '';
                        }

                        return $next($message);
                    })
                    ->with(function($message, \Closure $next) use (&$mpServicer, &$request){
                        $mp_open_id = $message->FromUserName;
                        // 处理消息
                        if($message->MsgType == 'text'){
                            $chat_content = $message->Content;

                            if($chat_content == '退订'){
                                update_user_meta(WxUser::withTrashed()->where('weixin_mp_openid', $mp_open_id)->value('id'), 'is_mp_free_publish_notice', 2, 'n');
                                return [
                                    "MsgType" => "text",
                                    "Content" => '退订成功，不再收到公众号的推文提醒，输入“订阅推文”，可重新订阅'
                                ];
                            }else if($chat_content == '订阅推文'){
                                update_user_meta(WxUser::withTrashed()->where('weixin_mp_openid', $mp_open_id)->value('id'), 'is_mp_free_publish_notice', 1, 'n');
                                return [
                                    "MsgType" => "text",
                                    "Content" => '订阅成功'
                                ];
                            }

                            $query = "SELECT * FROM wx_mp_message_reply WHERE (type = 1 AND word = ?) OR (type = 3 AND word LIKE CONCAT('%', ?, '%')) OR (type = 2 AND ? LIKE CONCAT('%', word, '%'))";
                            $matches = DB::select($query, [$chat_content, $chat_content,$chat_content]);
                            foreach ($matches as $record) {
                                $mp_message = WxMpMessage::find($record->mp_message_id);
                                if($mp_message){
                                    return $mp_message->normal();
                                }
                            }
                            return '';
                        }
                        return $next($message);
                    })
                    ->with(function($message, \Closure $next) use (&$mpServicer){
                        // 处理客服消息
                        return '';
                        return $next($message);
                    });

                return $mpServicer->response($request);
            }
        }
    }

}
